package bind

import (
	"fmt"

	"gitee.com/krio/ginc/example/dto/api/route"
	"gitee.com/krio/ginc/example/router/middleware"
	adminRoute "gitee.com/krio/ginc/example/router/serve/admin/route"
	"gitee.com/krio/ginc/example/router/warp"
	"gitee.com/krio/ginc/example/util/cmdprint"
	"github.com/gin-gonic/gin"
)

// ApiBind 接口相关绑定
func ApiBind(engine *gin.Engine) {
	// 绑定proto自动生成的接口
	for _, api := range route.GetGenApiRouteList() {
		err := formatApiBind(engine, api)
		if err != nil {
			cmdprint.CmdFatal(err.Error())
			return
		}
	}
	err := adminRoute.SetAdmin(engine)
	if err != nil {
		cmdprint.CmdFatal(err.Error())
		return
	}
}

// FormatApiBind 格式化接口路由
func formatApiBind(engine *gin.Engine, api route.IApiRoute) error {
	var (
		info     = api.GetInfo()
		handlers []gin.HandlerFunc
	)
	// 限流器
	handlers = append(handlers, middleware.Limiter(&middleware.LimitOption{
		Type:         middleware.LimitType(info.Limiter.Type),
		Mode:         middleware.LimitMode(info.Limiter.Mode),
		Cap:          info.Limiter.Cap,
		IntervalTime: info.Limiter.IntervalTime,
		ExpireTime:   info.Limiter.ExpireTime,
	}))

	// 接口中间件
	for _, mid := range info.Middlewares {
		switch mid {
		case middleware.MiddlewareKeyToken:
			handlers = append(handlers, middleware.JWTAuth)
		case middleware.MiddlewareKeyNoCache:
			handlers = append(handlers, middleware.NoCache)
		case middleware.MiddlewareKeyAdminAuth:
			handlers = append(handlers, middleware.AdminAuth)
		}
	}

	// 处理接口函数处理器（注意此处理器需要在中间件之后）
	handlers = append(handlers, warp.WrapHandler(api.GetFunc()))
	var (
		url    = api.GetURL()
		method = info.Method
	)
	switch method {
	case "GET":
		engine.GET(url, handlers...)
	case "POST":
		engine.POST(url, handlers...)
	case "DELETE":
		engine.DELETE(url, handlers...)
	case "PUT":
		engine.PUT(url, handlers...)
	case "PATCH":
		engine.PATCH(url, handlers...)
	default:
		return fmt.Errorf("不支持的接口类型: %+v", api.GetInfo())
	}
	return nil
}
